/**
 * hook_interpose.c - 通用函数拦截机制
 * 
 * 提供简单的宏和工具函数，让用户能够轻松拦截任何函数
 * 无需了解LD_PRELOAD的具体细节
 */

#define _GNU_SOURCE
#include <stdio.h>
#include <stdlib.h>
#include <dlfcn.h>
#include <string.h>
#include <pthread.h>
#include <stdarg.h>

#include "../../include/hook_framework.h"

/* ===== 线程本地存储 ===== */

// 防止递归调用
static __thread int tls_hook_active = 0;

/**
 * 检查当前钩子是否活跃（防递归）
 */
int is_hook_active(void) {
    return tls_hook_active;
}

/**
 * 设置钩子活跃状态
 */
void set_hook_active(int active) {
    tls_hook_active = active;
}

/* ===== 通用拦截辅助函数 ===== */

/**
 * 通用拦截包装器
 * 
 * 这个函数实现了通用的函数拦截逻辑：
 * 1. 创建上下文
 * 2. 调用前置回调
 * 3. 调用原始函数
 * 4. 调用后置回调
 * 5. 返回结果
 * 
 * 用户需要提供适当的参数处理逻辑
 */
void* generic_hook_wrapper(const char* func_name, void* original_func, int arg_count, ...) {
    // 防止递归调用
    if (is_hook_active()) {
        // 直接调用原始函数
        va_list args;
        va_start(args, arg_count);
        
        void* result = NULL;
        
        switch (arg_count) {
            case 0:
                result = ((void* (*)())original_func)();
                break;
            case 1:
                result = ((void* (*)(void*))original_func)(va_arg(args, void*));
                break;
            case 2:
                result = ((void* (*)(void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*));
                break;
            case 3:
                result = ((void* (*)(void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*));
                break;
            case 4:
                result = ((void* (*)(void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*));
                break;
            case 5:
                result = ((void* (*)(void*, void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*), va_arg(args, void*));
                break;
            case 6:
                result = ((void* (*)(void*, void*, void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*));
                break;
            // 可以根据需要添加更多参数
            default:
                log_message(LOG_ERROR, "不支持的参数数量: %d", arg_count);
                break;
        }
        
        va_end(args);
        return result;
    }
    
    // 设置活跃状态
    set_hook_active(1);
    
    // 检查钩子点是否启用
    if (!is_hook_point_enabled(func_name)) {
        // 钩子点禁用，直接调用原始函数
        va_list args;
        va_start(args, arg_count);
        
        void* result = NULL;
        
        switch (arg_count) {
            case 0:
                result = ((void* (*)())original_func)();
                break;
            case 1:
                result = ((void* (*)(void*))original_func)(va_arg(args, void*));
                break;
            case 2:
                result = ((void* (*)(void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*));
                break;
            case 3:
                result = ((void* (*)(void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*));
                break;
            case 4:
                result = ((void* (*)(void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*));
                break;
            case 5:
                result = ((void* (*)(void*, void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*), va_arg(args, void*));
                break;
            case 6:
                result = ((void* (*)(void*, void*, void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*));
                break;
            // 可以根据需要添加更多参数
            default:
                log_message(LOG_ERROR, "不支持的参数数量: %d", arg_count);
                break;
        }
        
        va_end(args);
        set_hook_active(0);
        return result;
    }
    
    // 创建上下文
    hook_context_t* context = create_context(func_name);
    if (!context) {
        // 创建上下文失败，直接调用原始函数
        va_list args;
        va_start(args, arg_count);
        
        void* result = NULL;
        
        switch (arg_count) {
            case 0:
                result = ((void* (*)())original_func)();
                break;
            case 1:
                result = ((void* (*)(void*))original_func)(va_arg(args, void*));
                break;
            case 2:
                result = ((void* (*)(void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*));
                break;
            case 3:
                result = ((void* (*)(void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*));
                break;
            case 4:
                result = ((void* (*)(void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*));
                break;
            case 5:
                result = ((void* (*)(void*, void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*), va_arg(args, void*));
                break;
            case 6:
                result = ((void* (*)(void*, void*, void*, void*, void*, void*))original_func)(
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*), 
                    va_arg(args, void*), va_arg(args, void*), va_arg(args, void*));
                break;
            // 可以根据需要添加更多参数
            default:
                log_message(LOG_ERROR, "不支持的参数数量: %d", arg_count);
                break;
        }
        
        va_end(args);
        set_hook_active(0);
        return result;
    }
    
    // 保存参数
    va_list args;
    va_start(args, arg_count);
    
    for (int i = 0; i < arg_count && i < 8; i++) {
        context->args[i] = va_arg(args, void*);
    }
    
    context->arg_count = arg_count;
    va_end(args);
    
    // 查找钩子点
    hook_point_t* hook_point = find_hook_point(func_name);
    
    // 执行前置回调
    int continue_exec = execute_pre_callbacks(hook_point, context);
    
    void* result = NULL;
    
    if (continue_exec) {
        // 调用原始函数
        switch (arg_count) {
            case 0:
                result = ((void* (*)())original_func)();
                break;
            case 1:
                result = ((void* (*)(void*))original_func)(context->args[0]);
                break;
            case 2:
                result = ((void* (*)(void*, void*))original_func)(
                    context->args[0], context->args[1]);
                break;
            case 3:
                result = ((void* (*)(void*, void*, void*))original_func)(
                    context->args[0], context->args[1], context->args[2]);
                break;
            case 4:
                result = ((void* (*)(void*, void*, void*, void*))original_func)(
                    context->args[0], context->args[1], context->args[2], context->args[3]);
                break;
            case 5:
                result = ((void* (*)(void*, void*, void*, void*, void*))original_func)(
                    context->args[0], context->args[1], context->args[2], context->args[3],
                    context->args[4]);
                break;
            case 6:
                result = ((void* (*)(void*, void*, void*, void*, void*, void*))original_func)(
                    context->args[0], context->args[1], context->args[2], context->args[3],
                    context->args[4], context->args[5]);
                break;
            // 可以根据需要添加更多参数
            default:
                log_message(LOG_ERROR, "不支持的参数数量: %d", arg_count);
                break;
        }
        
        // 保存结果
        context->result = result;
    }
    
    // 设置结束时间
    context->end_time = get_current_timestamp_ms();
    
    // 执行后置回调
    execute_post_callbacks(hook_point, context);
    
    // 保存可能被回调修改的结果
    result = context->result;
    
    // 销毁上下文
    destroy_context(context);
    
    // 重置活跃状态
    set_hook_active(0);
    
    return result;
}

/**
 * 注册函数钩子
 * 
 * 这个函数简化了钩子点的注册过程
 */
int register_function_hook(const char* func_name, int type, int group) {
    // 获取原始函数指针
    void* original_func = get_original_function(func_name);
    if (!original_func) {
        log_message(LOG_ERROR, "注册函数钩子失败: 无法获取原始函数 %s", func_name);
        return 0;
    }
    
    // 注册钩子点
    return register_hook_point(func_name, type, group, original_func);
} 